<template>
<div>
  <div class="world" ref="worldref">
    <div class="score">score：{{score | 0}}</div>
    <div class="restart pointer" v-if="isStart" @click="restart">重新开始</div>
    <div class="start-screen" v-if="gameover">游戏结束</div>
    <div v-if="!isStart && modele">
      <div class="start-screen pointer fade-in-animation" @click="startgame" >点击开始</div>
    </div>
    <div class="explain"> 游戏说明：<br>
      <span>点击空格跳跃 不要触碰到障碍物！</span>
      <br>
      <span>触碰到障碍物游戏结束！</span>
    </div>
    <div class="modele" v-if="!modele">
      <div class="fade-in-animation">
        选择难度：
        <div @click="modele = 0.002">简单</div>
        <div @click="modele = 0.005">普通</div>
        <div @click="modele = 0.01">速度与激情！</div>
      </div>
    </div>
    <img :src="groundimg" ref="grounds1" class="ground" />
    <img :src="groundimg" ref="grounds2" class="ground" />
    <img :src="dinostationaryimg" class="dino" ref="dinoref" />
  </div>
</div>
</template>


<script setup>
import groundimg from "./assets/imgs/ground.png";
import cactusimg from "./assets/imgs/cactus.png";
import dinoloseimg from "./assets/imgs/dino-lose.png";
import dinorun0img from "./assets/imgs/dino-run-0.png";
import dinorun1img from "./assets/imgs/dino-run-1.png";
import dinostationaryimg from "./assets/imgs/dino-stationary.png";
import { onMounted, ref, onBeforeUnmount } from "vue";
const worldWidth = 100;
const worldHeight = 500;
const worldref = ref(null);
const grounds1 = ref(null);
const grounds2 = ref(null);
const dinoref = ref(null);
const isStart = ref(false);
const gameover = ref(false);
let modele = ref(null);
let score = ref(0);
let isjumping = ref(false);
let dinoFrameCounter = ref(0);
setPixelToWorldScale(); // 初始化游戏世界的大小
window.addEventListener("resize", setPixelToWorldScale);

onMounted(() => {
  console.log(dinoref.value.src);
  document.addEventListener("keydown", handleJump);
  grounds1.value.style.left = 0;
  console.log(grounds1.value.width, 'grounds1.value.style.width');
  grounds2.value.style.left = grounds1.value.width / 2 + "px";
})

onBeforeUnmount(() => {
  document.removeEventListener('keydown', handleJump)
})
// 开始游戏
function startgame() {
  isStart.value = true;
  console.log("开始游戏");
  window.requestAnimationFrame(update);
  randomCactus();
  scoretimer();
}

function restart() {
  isStart.value = false;
  console.log("重新开始");
  window.location.reload();
}
// 地面移动
let groundSpeed = 1;
function moveGround(delta) {
  grounds1.value.style.left = parseInt(grounds1.value.style.left) - groundSpeed * delta * 0.5 -1 + "px";
  if (parseInt(grounds1.value.style.left) <= -2000) {
    grounds2.value.style.left = parseInt(grounds2.value.style.left) - groundSpeed * delta * 0.5 -1 + "px";
    if (parseInt(grounds2.value.style.left) <= -1200) {
      grounds1.value.style.left = 0;
      grounds2.value.style.left = grounds1.value.width / 2 + "px";
    }
  }
  // 每隔15秒增加地面移动速度
  if (score.value % 15 == 0 && score.value != 0) {
    groundSpeed += modele.value;
  }
}

// 创建仙人掌
function createCactus() {
  const cactus = document.createElement('img');
  cactus.src = cactusimg;
  cactus.classList.add('cactus');
  cactus.style.position = 'absolute';
  cactus.style.left = '2000px';
  cactus.style.width = '40px';
  cactus.style.height = '80px';
  cactus.style.bottom = '0';
  document.querySelector('.world').appendChild(cactus);
}

// 仙人掌移动
function moveCactus(delta) {
  const cactus = document.querySelector('.cactus');
  // 移动仙人掌
  if (cactus) {
    cactus.style.left = parseInt(cactus.style.left) - groundSpeed * delta * 0.5 -1 + "px";
    if (parseInt(cactus.style.left) <= -100) {
      cactus.remove();
    }
  }
}

// 计分
const scoretimer = ()=> {
  setInterval(() => {
    score.value += 1;
  }, 1000);
}

//3-4秒内随机生成仙人掌
function randomCactus() {
  const randomTime = Math.floor(Math.random() * 5) + 1;
  // const randomTime = Math.random() * 1000 + 1000 * 3;
  setTimeout(() => {
    console.log('生成仙人掌', randomTime);
    createCactus();
    randomCactus();
  }, randomTime * 1000);
}

//碰撞后小恐龙切换图片
async function changeDinoImg() {
  dinoref.value.src = dinoloseimg;
  dinoref.value.style.width = '80px';
  dinoref.value.style.height = '80px';
  gameover.value = true;
}

//游戏结束
async function gameOver() {
  window.location.reload();
}

// 检测碰撞
async function checkCollision() {
  const cactus = document.querySelector('.cactus');
  if (cactus && dinoref.value && isjumping.value) {
    const dinoRect = dinoref.value.getBoundingClientRect();
    const cactusRect = cactus.getBoundingClientRect();
    if (isCollision(dinoRect, cactusRect)) {
      console.log('碰撞了');
      await changeDinoImg();
      clearInterval(scoretimer);
      gameOver();
    }
  } else if (cactus && dinoref.value && !isjumping.value) {
    const dinoRect = dinoref.value.getBoundingClientRect();
    const cactusRect = cactus.getBoundingClientRect();
    if (isCollision(dinoRect, cactusRect)) {
      console.log('碰撞了');
      await changeDinoImg();
      clearInterval(scoretimer);
      gameOver();
    }
  }
}

// 检测碰撞
function isCollision(rect1, rect2) {
  return (
    rect1.left < rect2.right &&
    rect1.right > rect2.left &&
    rect1.top < rect2.bottom &&
    rect1.bottom > rect2.top
  );
}

// 小恐龙运动动画
function handleRun() { 
  if (isjumping.value) {
    dinoref.value.src = dinostationaryimg
  } else {
    if (dinoFrameCounter.value % 10 === 0) {
      dinoref.value.src = dinorun0img
      dinoref.value.style.width = '80px';
      dinoref.value.style.height = '80px';
    } 
    if (dinoFrameCounter.value % 10 === 5) {
      dinoref.value.src = dinorun1img
      dinoref.value.style.width = '80px';
      dinoref.value.style.height = '80px';
    }
    dinoFrameCounter.value++;
  }
}

// 小恐龙跳跃
function handleJump() {
  if (isjumping.value) {
    return;
  }
  console.log(isjumping.value, ' isjumping');
  isjumping.value = true;
  let jumpHeight = 300; // 跳跃高度
  let jumpDuration = 500; // 跳跃时间
  let jumpStart = Date.now();
  // let jumpEnd = jumpStart + jumpDuration;
  let jumpInterval = setInterval(() => {
    let now = Date.now();
    let progress = (now - jumpStart) / jumpDuration;
    if (progress >= 1) {
      clearInterval(jumpInterval);
      isjumping.value = false;
      dinoref.value.style.bottom = "0px";
    } else {
      let height = jumpHeight * Math.sin(Math.PI * progress);
      dinoref.value.style.bottom = height + "px";
    }
  }, 16); // 16ms 是浏览器刷新频率的一半，这样可以保证动画的流畅性
}

// 定义窗口高度和宽度
function setPixelToWorldScale() {
  let worldToPixeScale = 0;
  if (window.innerWidth / window.innerHeight < worldWidth / worldHeight) {
    worldToPixeScale = window.innerWidth / worldWidth;
  } else {
    worldToPixeScale = window.innerHeight / worldHeight;
  }
  if (worldref.value) {
    worldref.value.style.width = `${worldWidth * worldToPixeScale}px`;
    worldref.value.style.height = `${worldHeight * worldToPixeScale}px`;
  }
}

// 动画执行函数
let lastTime; // 上一次动画执行时间
function update(time) {
  // 动画开始执行时，lastTime是为null，所以需要对齐赋值
  if (lastTime == null) {
    lastTime = time;
    window.requestAnimationFrame(update);
    return;
  }
  const delta = time - lastTime; // 计算上一次动画时间和本次动画时间差
  console.log(delta, "delta");
  moveGround(delta);
  handleRun()
  moveCactus(delta);
  checkCollision();
  lastTime = time;
  window.requestAnimationFrame(update);
}

</script>

<style lang="less" scoped>
.world {
  position: relative;
  overflow: hidden;
    width: 100%;
    height: 600px;
  }
  @keyframes fadeIn {  
    from {  
      opacity: 0; /* 初始状态为不可见 */  
    }  
    to {  
      opacity: 1; /* 最终状态为可见 */  
    }  
  }  
    
  .fade-in-animation {  
    opacity: 0; /* 初始状态为不可见 */  
    animation: fadeIn 1.5s ease-in-out forwards; /* 应用动画，持续时间为2秒，使用ease-in-out缓动函数，并在动画结束后保持最终状态 */  
  }  
    
  .explain{
    font-size: 1.25rem;
    font-weight: 700;
    margin-top: 1rem;
    margin-left: 1rem;
  }
  .modele{
    font-size: 1.75rem;
    font-weight: 500;
    text-align: center;
    margin: 1rem auto;
    margin-top: 3rem;
    cursor: pointer;
  }
  .score {
    position: absolute;
    top: .5rem;
    right: .5rem;
    font-size: 1.5rem;
  }
  .restart{
    position: absolute;
    top: 3.5rem;
    right: 1rem;
    font-size: 1.5rem;
  }
  .start-screen {
    position: absolute;
    top: 40%;
    left: 48%;
    font-size: 1.75rem;
  }
  
  .hine {
    display: none;
  }
  
  .ground {
    position: absolute;
    width: 300%;
    bottom: 0;
    left: 0;
  }
  
  .dino {
    position: absolute;
    left: 10px;
    height: 80px;
    width: 80px;
    bottom: 0;
  }
  
  .cactus {
    position: absolute;
    left: 0;
    height: 30%;
    bottom: 0;
  }  
  .pointer {
    cursor: pointer;
  }

</style>